package myJs.cps.project

import myJs.api.Api
import myJs.cps.BootstrapTableCp.Column
import myJs.cps.{BootstrapTableCp, Style}
import myJs.myPkg.reactBootstrap.{OverlayTrigger, Popover}
import myJs.tool.Pojo.{ExportData, NumericSearch, TextSearch}
import slinky.core.FunctionalComponent
import slinky.core.annotations.react
import slinky.core.facade.Hooks.{useEffect, useState}
import slinky.core.facade.ReactElement
import slinky.web.html._
import typings.csstype.csstypeStrings
import upickle.default.{reader, writeJs}

import scala.collection.immutable.SeqMap
import scala.scalajs.js
import myJs.Implicits._
import org.scalajs.macrotaskexecutor.MacrotaskExecutor.Implicits._

/** Created by yz on 21/1/2022
  */
@react object CellTypeCp {

  case class Props(kind: String)

  val component = FunctionalComponent[Props] { props =>
    val (datas, setDatas) = useState(List.empty[ujson.Obj])
    val (columns, setColumns) = useState(List.empty[Column])

    object FTool {

      def refreshColumns = () => {
        val map = SeqMap(
          "lineage" -> "Lineage",
          "clusterResolution" -> "Resolution",
          "cellType" -> "Cell_Type",
          "suggestedLabels" -> "Suggested Labels",
          "featureGenes" -> "Feature Genes",
          "freq" -> "Freq"
        )
        val basicColumns = map.map { case (k, v) =>
          val searchKind = v match {
            case "Freq" => NumericSearch
            case _ => TextSearch
          }
          val title = v
          val fmt = FTool.tbFmt(k)
          val comVF = FTool.comVFmt(v)
          Column(field = k, title = title, operable = true, searchKind = searchKind, formatter = fmt, comVF = comVF)
        }.toList
        setColumns(basicColumns)
      }

      def refreshTableB = () => {
        Api.browseGene.cellType(props.kind).map { response =>
          val curDatas = response
          val datas = curDatas.map(x => writeJs(x).transform(reader[ujson.Obj]))
          setDatas(datas)
        }
      }

      def tbFmt(field: String) = (v: ujson.Value, row: ujson.Obj) => {
        field match {
          case "featureGenes" =>
            val es = v.str.split(";").toList.zipWithIndex.map { case (x, curI) =>
              span(
                key := s"${curI}",
                style := Style(
                  paddingTop = 0,
                  paddingBottom = 0,
                  paddingLeft = 7,
                  paddingRight = 7,
                  borderRadius = 0,
                  marginRight = 8,
                  marginBottom = 2,
                  background = "#fafafa"
                ),
                className := "gene_tag disabled btn btn-default btn-xs",
                x
              )
            }
            span(es)()
          case _ => span(v.myStr)()
        }
      }

      def comVFmt(fileTitle: String) = (v: ujson.Value, row: ujson.Obj) => {
        fileTitle match {
          case _ => v.myStr
        }
      }

    }

    useEffect(
      () => {
        FTool.refreshColumns()
      },
      List()
    )

    useEffect(
      () => {
        FTool.refreshTableB()
      },
      List(props.kind)
    )

    val exportDatas = List(
      ExportData("XLSX", href = s"${Api.apiUrl}/gepLiver/tool/downloadFile?fileName=Cell_Type.xlsx")
    )

    div(
      style := Style(),
      h5(
        style := Style(marginBottom = 15, fontSize = 16, marginTop = 15),
        id := "sCell",
        "Cell Type ", {
          val popover: ReactElement = Popover(id = "popover-basic")(
            Popover.Title("Note"),
            Popover.Content(
              "Information of clusters and cell types with percentage and feature genes annotated"
            )
          )
          OverlayTrigger(
            placement = "right",
            trigger = js.Array("focus", "hover"),
            overlay = popover
          )(
            span(
              a(`type` := "button", i(className := "fas fa-info-circle"))
            )
          )
        }
      ),
      BootstrapTableCp(
        columns = columns,
        datas = datas,
        pageList = List(5, 10, 25, 50),
        pageSize = 5,
        showExport = true,
        exportData = exportDatas,
        selectColumnEnabled = true
      )
    )

  }

  object STool {

    val myBtn =
      Style(cursor = csstypeStrings.pointer, marginBottom = 10, paddingTop = 3, paddingBottom = 3, marginRight = 15)

  }

}
